#ifndef PARSEPAT_H
#define PARSEPAT_H
#include <stdio.h>
#include <string.h>

#define PAT_PROGRAM_MAX 512

typedef struct TS_PAT_PROGRAM
{
    unsigned int program_number :16;
    unsigned int reserved_3 :3;
    unsigned int program_map_PID :13;
} TS_PAT_PROGRAM;

typedef struct TS_PAT
{
    unsigned int table_id :8;
    unsigned int section_syntax_indicator :1;
    unsigned int zero :1;
    unsigned int reserved_1 :2;
    unsigned int section_length :12;
    unsigned int transport_stream_id :16;
    unsigned int reserved_2 :2;
    unsigned int version_number :5;
    unsigned int current_next_indicator :1;
    unsigned int section_number :8;
    unsigned int last_section_number :8;

    TS_PAT_PROGRAM astPAT_Program[PAT_PROGRAM_MAX];

    unsigned int network_PID :13;
    unsigned int CRC_32 :32;
} TS_PAT;

/*----------------------------------------------------------*/
/* the information we want to get form the PAT table */
/*----------------------------------------------------------*/
typedef struct PAT_INFO
{
    unsigned int uiProgramNumber :16;
    unsigned int uiPMT_PID :13;
} PAT_INFO;

class ParsePAT
{
public:
    ~ParsePAT();
    ParsePAT(const ParsePAT&)=delete;
    ParsePAT& operator=(const ParsePAT&)=delete;
    static ParsePAT& get_instance();

    /*********************************************************************************************************************************
     * Function Name : ParsePAT_Table
     * Description   :  parse the PAT table put the information in PAT_INFO
     * Parameters    :
     * 				pfTsFile -- the TS file descriptor
     * 				iTsPosition -- the TS package begin position
     *				iTsLength -- the TS package length
     *				pstPAT_Info -- the PAT_INFO array
     * Returns       :-1 - failure  >=0 - the count of the program
     *********************************************************************************************************************************/
    int ParsePAT_Table(FILE *pfTsFile, int iTsPosition, int iTsLength, PAT_INFO *pstPAT_Info);
private:
    /*********************************************************************************************************************************
     * Function Name : ParsePAT_SectionHead
     * Description   :  parse the PAT section head
     * Parameters    :
     * 				pstTS_PAT -- the TS_PAT
     *				pucSectionBuffer -- the PAT section buffer
     * Returns       : void
     *********************************************************************************************************************************/
    void ParsePAT_SectionHead(TS_PAT *pstTS_PAT, unsigned char *pucSectionBuffer);
    /*********************************************************************************************************************************
     * Function Name : ParsePAT_Section
     * Description   :  parse the PAT section
     * Parameters    :
     * 				pstTS_PAT -- the TS_PAT
     *				pucSectionBuffer -- the PAT section buffer
     * Returns       : the PAT_PROGRAM count
     *********************************************************************************************************************************/
    int ParsePAT_Section(TS_PAT *pstTS_PAT, unsigned char *pucSectionBuffer);
    /*********************************************************************************************************************************
     * Function Name : GetPAT_Info
     * Description   :  get the PAT information (program_number and PMT_PID)
     * Parameters    :
     * 				pstTS_PAT -- the TS_PAT
     * 				iPAT_ProgramCount -- PAT_PROGRAM count
     *				pstPAT_Info -- the PAT_INFO array
     *				iInfoCount -- the PAT_INFO count
     * Returns       : void
     *********************************************************************************************************************************/
    void GetPAT_Info(TS_PAT *pstTS_PAT, int iPAT_ProgramCount, PAT_INFO *pstPAT_Info, int *iInfoCount);
    /*********************************************************************************************************************************
     * Function Name : CleanPAT_Info
     * Description   :  clean PAT information
     * Parameters    :
     *				pstPAT_Info -- the PAT_INFO array
     *				piInfoCount -- the PAT_INFO count
     * Returns       : void
     *********************************************************************************************************************************/
    void CleanPAT_Info(PAT_INFO *pstPAT_Info, int *piInfoCount);
private:
    ParsePAT();
};

#endif // PARSEPAT_H
